home *** CD-ROM | disk | FTP | other *** search
/ Aminet 32 / Aminet 32 (1999)(Schatztruhe)[!][Aug 1999].iso / Aminet / dev / c / SUPRALib.lha / SUPRALib / Developer / Source.ORG / MakeNewImg.c < prev    next >
C/C++ Source or Header  |  1999-05-17  |  5KB  |  147 lines

  1. /****** MakeNewImg *************************************************
  2. *
  3. *   NAME
  4. *       MakeNewImg -- Remap an image to any new colours (V10)
  5. *
  6. *   SYNOPSIS
  7. *       newImage = MakeNewImg(oldImage, palette)
  8. *
  9. *       struct Image * = MakeNewImg(struct Image *, ULONG *);
  10. *
  11. *   FUNCTION
  12. *       This function creates a new clone image of a provided
  13. *       image, and it remaps the new image according to a provided
  14. *       pen colour list.
  15. *       This is very useful when you need your image to use
  16. *       specific colours anywhere in the available palette.
  17. *       (e.g. you obtained some free pens from a palette, and
  18. *       you want your image to be shown with those pens).
  19. *       It is possible to modify an image's pens with PlanePick and
  20. *       PlaneOnOff fields (see Image structure), but this has a major
  21. *       limitation: most colour combinations are not possible to get.
  22. *
  23. *       If your image has four colours (0,1,2,3), and you want to
  24. *       remap these to (0,16,4,7), you simply call this function,
  25. *       providing it with the image and a new colour map, and a
  26. *       new image will be created for you.
  27. *
  28. *   INPUTS
  29. *       oldImage - pointer to an Image structure to be remapped
  30. *       palette  - pointer to a list of new pens
  31. *
  32. *       A pens list should contain the exact number of pens as
  33. *       an old image uses. (2 if image's depth is 1, 4 if image's
  34. *       depth is 2, etc.). An image's colour 0 will be remapped to the
  35. *       first pen on the list, image's colour 1 will be remapped to
  36. *       the second pen on the list and so on.
  37. *
  38. *   RESULT
  39. *       newImage - pointer to a newly initialized remapped old image's
  40. *                  clone. If there is not enough memory, newImage will
  41. *                  be NULL.
  42. *       IMPORTANT: If a new image was created you have to call
  43. *       FreeNewImg() to free the allocated memory, when you no longer
  44. *       need to use it!
  45. *
  46. *   EXAMPLE
  47. *
  48. *       We have a depth 2 image (4 colours), and we want to use pens
  49. *       0,16,4,7 instead of 0,1,2,3:
  50. *
  51. *
  52. *       struct Image OldImage = {
  53. *           ....    \* This is a data of our original image *\
  54. *
  55. *       struct Image *NewImage;
  56. *       ULONG pal[] = {0, 16, 4, 7}; \* The new pen list *\
  57. *
  58. *       if (NewImage = MakeNewImg(&OldImage, &pal[0])) {
  59. *          DrawImage(rp, NewImage);
  60. *          FreeNewImg(NewImage);    \* We will no longer use it *\
  61. *       }
  62. *
  63. *   NOTE
  64. *       A new image's depth will change to a depth that can hold
  65. *       the largest pen number from a pens list. It does not have
  66. *       any smart routine to check if the depth can be optimized
  67. *       down, by altering PlanePick and PlaneOnOff, yet.
  68. *       Bear in mind that if you provide a pen 255, then a new image's
  69. *       depth will be at least 8.
  70. *
  71. *       You MUST free a new image with FreeNewImg() when it's no longer
  72. *       needed!
  73. *
  74. *       This function can take much time when remapping larger images
  75. *       with more depths.
  76. *
  77. *   BUGS
  78. *       None found.
  79. *
  80. *   SEE ALSO
  81. *       FreeNewImg()
  82. *
  83. **********************************************************************/
  84.  
  85. #include<proto/exec.h>
  86. #include<exec/exec.h>
  87. #include<intuition/intuition.h>
  88.  
  89. char __asm mkImg(register __a1 UWORD *,
  90.                     register __a2 UWORD *,
  91.                     register __a3 ULONG *,
  92.                     register __d4 LONG,
  93.                     register __d5 LONG,
  94.                     register __d6 LONG);
  95.  
  96. struct Image *MakeNewImg(struct Image *img, ULONG *pal)
  97. {
  98. struct Image *newimg;
  99. UWORD i, num, max=0, dep;
  100. WORD wid;
  101. LONG mask=0;
  102.  
  103.     if (newimg = AllocMem(sizeof(struct Image), 0)) {
  104.         dep = img->Depth;
  105.         num = 1<<dep;
  106.  
  107.         /* Get the maximum palette color entry */
  108.         for (i=0; i<num; i++) if (pal[i] > max) max = pal[i];
  109.  
  110.         /* Get a destination depth */
  111.         while (max>>dep > 0) dep++;
  112.  
  113.         /* Width must be word aligned */
  114.         i=0;
  115.         wid = img->Width;
  116.         while(i < wid) i+=16;
  117.         wid = i; /* NOTE: Width=0 is not considered yet */
  118.  
  119.         /* Alloc Planes */
  120.         if (newimg->ImageData = AllocMem(img->Height*wid*dep/8, MEMF_CHIP | MEMF_CLEAR)) {
  121.             /* Fill newimg fields */
  122.  
  123.             newimg->Depth = dep;
  124.             newimg->Height = img->Height;
  125.             newimg->Width = img->Width;
  126.             newimg->LeftEdge = img->LeftEdge;
  127.             newimg->TopEdge = img->TopEdge;
  128.             for (i=0; i<dep; i++) mask |= 1<<i;
  129.             newimg->PlanePick = mask;
  130.             newimg->PlaneOnOff = 0;
  131.             newimg->NextImage = NULL;
  132.  
  133.             mkImg(img->ImageData, newimg->ImageData, pal,
  134.                      img->Height*wid/8, img->Depth, dep);
  135.  
  136.         }
  137.     }
  138.  
  139.     if (newimg) {
  140.         if (newimg->ImageData) return(newimg);
  141.         else {
  142.             FreeMem(newimg, sizeof(struct Image));
  143.             return(NULL);
  144.         }
  145.     } else return(NULL);
  146. }
  147.